#ifndef __AWOS_ASM_H__
#define __AWOS_ASM_H__

#include <kernel.h>

static inline void outportb(unsigned short port, unsigned char byte)
{
	asm volatile(
		  "outb %0, %1"
		:
		: "a" (byte), "Nd" (port)
	);
	
	return;
}

static inline void outportw(unsigned short port, unsigned short word)
{
	asm volatile(
		  "outw %0, %1"
		:
		: "a" (word), "Nd" (port)
	);
	
	return;
}

static inline void outportl(unsigned short port, unsigned int dword)
{
	asm volatile(
		  "outl %0, %1"
		:
		: "a" (dword), "Nd" (port)
	);
	
	return;
}

static inline unsigned char inportb(unsigned short port)
{
	register unsigned char byte;
	
	asm volatile(
		  "inb %1, %0"
		: "=a" (byte)
		: "Nd" (port)
	);
	
	return byte;
}

static inline unsigned short inportw(unsigned short port)
{
	register unsigned short word;
	
	asm volatile(
		  "inw %1, %0"
		: "=a" (word)
		: "Nd" (port)
	);
	
	return word;
}

static inline unsigned int inportl(unsigned short port)
{
	register unsigned int dword;
	
	asm volatile(
		  "inl %1, %0"
		: "=a" (dword)
		: "Nd" (port)
	);
	
	return dword;
}

static inline unsigned char inportb_p(unsigned short port)
{
	register unsigned char byte;
	
	asm volatile
	(
		  "inb  %1, %0   \n"
		  "outb %%al, $0x80"
		: "=a" (byte)
		: "Nd" (port)
	);
	
	return byte;
}

static inline void outportb_p(unsigned short port, unsigned char byte)
{
	asm volatile
	(
		  "outb %0, %1   \n"
		  "outb %%al, $0x80"
		:
		: "a" (byte), "Nd" (port)
	);
	
	return;
}

static inline void inportw_string(unsigned short port, unsigned int count, unsigned short *buf)
{
	asm volatile (
		  "rep ; insw"
		: "=D" (buf), "=c" (count)
		: "d" (port), "0" (buf), "1" (count)
	);
	
	return;
}

static inline void outportw_string(unsigned short port, unsigned int count, unsigned short *addr)
{
	asm volatile (
		  "rep ; outsw"
		: "=S" (addr), "=c" (count)
		: "d" (port), "0" (addr), "1" (count)
	);
	
	return;
};

static inline void halt()
{
	asm volatile ("hlt");
	
	return;
}

static inline void cli()
{
	asm volatile ("cli");
	
	return;
}

static inline void sti()
{
	asm volatile ("sti");
	
	return;
}

#endif
